import { EventDispatcher } from './EventDispatcher'

/**
 * 硫酸装置跨域、跨窗口通信接口
 * 使用方式：
 * const api = new IframePostMessageApi();
 * 监听子页面事件：
 * api.addEventListener('on_focus', (event) => {  });
 * api.addEventListener('on_leave', (event) => {  });
 * api.addEventListener('on_view_change', (event) => {  });
 * 发送给子页面事件：
 * api.sendAllAlarmMessage(targetWindow, list);
 * api.sendUpdateAlarmMessage(targetWindow, list);
 * api.sendRemoveAlarmMessage(targetWindow, target);
 * api.sendFocusMessage(targetWindow, target);
 * api.sendViewBackMessage(targetWindow, toTopLevel);
 */
export class IframePostMessageApi extends EventDispatcher {

    constructor() {
        super();
        this.startListenMessage();
    }
    private fn: any;

    /**
     * 发送全量告警数据列表（覆盖更新）
     * @param {Window} targetWindow html中的iframe元素的窗口或父级窗口，iframe.contentWindow or window.parent
     * @param {Array} list 报警数据列表
     */
    sendAllAlarmMessage(targetWindow: any, list: any) {
        this.send(targetWindow, { event: "reset_alarm", list: list });
    }

    /**
     * 发送新的告警数据列表（增量更新）
     * @param {Window} targetWindow html中的iframe元素的窗口或父级窗口，iframe.contentWindow or window.parent
     * @param {Array} list 报警数据列表
     */
    sendUpdateAlarmMessage(targetWindow: any, list: any) {
        this.send(targetWindow, { event: "update_alarm", list: list });
    }

    /**
     * 发送移除告警数据的消息
     * @param {Window} targetWindow html中的iframe元素的窗口或父级窗口，iframe.contentWindow or window.parent
     * @param {Array} target 设备号，区域编码，或位号
     */
    sendRemoveAlarmMessage(targetWindow: any, target: any) {
        this.send(targetWindow, { event: "remove_alarm", target: target });
    }

    /**
     * 找到目标并聚焦到目标位置
     * @param {Window} window html中的iframe元素的窗口或父级窗口，iframe.contentWindow or window.parent
     * @param {string} target 设备号，区域编码，或位号
     */
    sendFocusMessage(targetWindow: any, target: any) {
        this.send(targetWindow, { event: "focus", target: target });
    }

    /**
     * 通知视角还原
     * @param {Window} window html中的iframe元素的窗口或父级窗口，iframe.contentWindow or window.parent
     */
    sendViewBackMessage(targetWindow: any, toTopLevel: any) {
        this.send(targetWindow, { event: "view_back", top: !!toTopLevel });
    }

    send(targetWindow: any, value: any) {
        targetWindow.postMessage(typeof value === 'string' ? value : JSON.stringify(value), '*');
    }

    startListenMessage() { 
        if (window && window.addEventListener) { 
            this.fn = this.onMessage.bind(this); // 使this指针不会指向window
            window.addEventListener("message", this.fn); 
        } else {
            console.log("[IframePostMessageApi] 开始监听消息失败，需要在浏览器中运行！");
        }
    }
    
    stopListenMessage() {
        if (window && window.removeEventListener) {
            window.removeEventListener("message", this.fn); 
        }
    }

    onMessage(event: any) {
        try {
            const message = JSON.parse(event.data);
            console.log(`[IframePostMessageApi] 接收到来自"${event.origin}"的消息:${event.data}`);
            this.dispatchEvent({
                target: this,
                type: message.event,
                message: message
            });
        } catch (e: any) {
            // ignored
            if (e.name !== "SyntaxError") {
                console.log(e);
            }
        }
    }

}
